/**
 * 手势处理模块
 * 处理触摸手势、鼠标事件、键盘事件等
 */

window.ComicReader = window.ComicReader || {};

ComicReader.GestureHandler = class {
    constructor(element, options = {}) {
        this.element = element;
        this.options = {
            // 滑动相关
            swipeThreshold: 50,          // 滑动最小距离
            swipeTimeout: 300,           // 滑动最大时间
            swipeVelocity: 0.3,          // 滑动最小速度
            
            // 点击相关
            tapThreshold: 10,            // 点击最大移动距离
            tapTimeout: 200,             // 点击最大时间
            doubleTapTimeout: 300,       // 双击间隔时间
            
            // 缩放相关
            scaleMin: 0.5,               // 最小缩放比例
            scaleMax: 3,                 // 最大缩放比例
            scaleSensitivity: 0.01,      // 缩放灵敏度
            
            // 长按相关
            longPressTimeout: 500,       // 长按时间
            
            ...options
        };
        
        this.state = {
            isDown: false,
            startX: 0,
            startY: 0,
            startTime: 0,
            lastTap: 0,
            scale: 1,
            translateX: 0,
            translateY: 0,
            isDragging: false,
            longPressTimer: null
        };
        
        this.callbacks = {};
        this.init();
    }
    
    init() {
        // 绑定事件
        this.bindEvents();
        
        // 防止默认行为
        this.element.style.touchAction = 'none';
        this.element.style.userSelect = 'none';
        this.element.style.webkitUserSelect = 'none';
    }
    
    bindEvents() {
        // 触摸事件
        this.element.addEventListener('touchstart', this.handleTouchStart.bind(this), { passive: false });
        this.element.addEventListener('touchmove', this.handleTouchMove.bind(this), { passive: false });
        this.element.addEventListener('touchend', this.handleTouchEnd.bind(this), { passive: false });
        this.element.addEventListener('touchcancel', this.handleTouchCancel.bind(this));
        
        // 鼠标事件
        this.element.addEventListener('mousedown', this.handleMouseDown.bind(this));
        this.element.addEventListener('mousemove', this.handleMouseMove.bind(this));
        this.element.addEventListener('mouseup', this.handleMouseUp.bind(this));
        this.element.addEventListener('mouseleave', this.handleMouseLeave.bind(this));
        
        // 滚轮事件（用于缩放）
        this.element.addEventListener('wheel', this.handleWheel.bind(this), { passive: false });
        
        // 键盘事件
        document.addEventListener('keydown', this.handleKeyDown.bind(this));
        
        // 阻止上下文菜单
        this.element.addEventListener('contextmenu', (e) => e.preventDefault());
    }
    
    // 触摸开始
    handleTouchStart(e) {
        e.preventDefault();
        
        const touch = e.touches[0];
        this.startGesture(touch.clientX, touch.clientY);
        
        // 多点触摸处理
        if (e.touches.length === 2) {
            this.handlePinchStart(e);
        }
    }
    
    // 触摸移动
    handleTouchMove(e) {
        e.preventDefault();
        
        if (e.touches.length === 1) {
            const touch = e.touches[0];
            this.moveGesture(touch.clientX, touch.clientY);
        } else if (e.touches.length === 2) {
            this.handlePinchMove(e);
        }
    }
    
    // 触摸结束
    handleTouchEnd(e) {
        e.preventDefault();
        
        if (e.changedTouches.length === 1) {
            const touch = e.changedTouches[0];
            this.endGesture(touch.clientX, touch.clientY);
        }
        
        // 清除长按定时器
        this.clearLongPress();
    }
    
    // 触摸取消
    handleTouchCancel(e) {
        this.cancelGesture();
    }
    
    // 鼠标按下
    handleMouseDown(e) {
        e.preventDefault();
        this.startGesture(e.clientX, e.clientY);
    }
    
    // 鼠标移动
    handleMouseMove(e) {
        if (this.state.isDown) {
            this.moveGesture(e.clientX, e.clientY);
        }
    }
    
    // 鼠标释放
    handleMouseUp(e) {
        this.endGesture(e.clientX, e.clientY);
    }
    
    // 鼠标离开
    handleMouseLeave(e) {
        if (this.state.isDown) {
            this.cancelGesture();
        }
    }
    
    // 滚轮事件
    handleWheel(e) {
        e.preventDefault();
        
        const delta = e.deltaY > 0 ? -0.1 : 0.1;
        const newScale = Math.max(
            this.options.scaleMin,
            Math.min(this.options.scaleMax, this.state.scale + delta)
        );
        
        if (newScale !== this.state.scale) {
            this.state.scale = newScale;
            this.trigger('scale', { scale: newScale, centerX: e.clientX, centerY: e.clientY });
        }
    }
    
    // 键盘事件
    handleKeyDown(e) {
        const key = e.key;
        
        switch (key) {
            case 'ArrowLeft':
                this.trigger('swiperight');
                break;
            case 'ArrowRight':
                this.trigger('swipeleft');
                break;
            case 'ArrowUp':
                this.trigger('swipedown');
                break;
            case 'ArrowDown':
                this.trigger('swipeup');
                break;
            case ' ':
                e.preventDefault();
                this.trigger('swipeleft');
                break;
            case 'Escape':
                this.trigger('escape');
                break;
        }
    }
    
    // 开始手势
    startGesture(x, y) {
        this.state.isDown = true;
        this.state.startX = x;
        this.state.startY = y;
        this.state.startTime = Date.now();
        this.state.isDragging = false;
        
        // 开始长按检测
        this.startLongPress();
        
        this.trigger('gesturestart', { x, y });
    }
    
    // 移动手势
    moveGesture(x, y) {
        if (!this.state.isDown) return;
        
        const deltaX = x - this.state.startX;
        const deltaY = y - this.state.startY;
        const distance = Math.sqrt(deltaX * deltaX + deltaY * deltaY);
        
        // 如果移动距离超过阈值，取消长按
        if (distance > this.options.tapThreshold) {
            this.clearLongPress();
            this.state.isDragging = true;
        }
        
        this.trigger('gesturemove', { x, y, deltaX, deltaY, distance });
    }
    
    // 结束手势
    endGesture(x, y) {
        if (!this.state.isDown) return;
        
        const deltaX = x - this.state.startX;
        const deltaY = y - this.state.startY;
        const deltaTime = Date.now() - this.state.startTime;
        const distance = Math.sqrt(deltaX * deltaX + deltaY * deltaY);
        
        this.state.isDown = false;
        this.clearLongPress();
        
        // 判断手势类型
        if (distance < this.options.tapThreshold && deltaTime < this.options.tapTimeout) {
            this.handleTap(x, y);
        } else if (deltaTime < this.options.swipeTimeout) {
            this.handleSwipe(deltaX, deltaY, deltaTime);
        }
        
        this.trigger('gestureend', { x, y, deltaX, deltaY, deltaTime, distance });
    }
    
    // 取消手势
    cancelGesture() {
        this.state.isDown = false;
        this.state.isDragging = false;
        this.clearLongPress();
        this.trigger('gesturecancel');
    }
    
    // 处理点击
    handleTap(x, y) {
        const now = Date.now();
        const isDoubleTap = (now - this.state.lastTap) < this.options.doubleTapTimeout;
        
        if (isDoubleTap) {
            this.trigger('doubletap', { x, y });
        } else {
            setTimeout(() => {
                if ((Date.now() - this.state.lastTap) >= this.options.doubleTapTimeout) {
                    this.trigger('tap', { x, y });
                }
            }, this.options.doubleTapTimeout);
        }
        
        this.state.lastTap = now;
    }
    
    // 处理滑动
    handleSwipe(deltaX, deltaY, deltaTime) {
        const absX = Math.abs(deltaX);
        const absY = Math.abs(deltaY);
        const velocity = Math.sqrt(deltaX * deltaX + deltaY * deltaY) / deltaTime;
        
        // 检查是否达到滑动阈值
        if (Math.max(absX, absY) < this.options.swipeThreshold) return;
        if (velocity < this.options.swipeVelocity) return;
        
        // 判断滑动方向
        if (absX > absY) {
            // 水平滑动
            if (deltaX > 0) {
                this.trigger('swiperight', { deltaX, deltaY, velocity });
            } else {
                this.trigger('swipeleft', { deltaX, deltaY, velocity });
            }
        } else {
            // 垂直滑动
            if (deltaY > 0) {
                this.trigger('swipedown', { deltaX, deltaY, velocity });
            } else {
                this.trigger('swipeup', { deltaX, deltaY, velocity });
            }
        }
    }
    
    // 开始长按检测
    startLongPress() {
        this.clearLongPress();
        this.state.longPressTimer = setTimeout(() => {
            if (this.state.isDown && !this.state.isDragging) {
                this.trigger('longpress', { x: this.state.startX, y: this.state.startY });
            }
        }, this.options.longPressTimeout);
    }
    
    // 清除长按检测
    clearLongPress() {
        if (this.state.longPressTimer) {
            clearTimeout(this.state.longPressTimer);
            this.state.longPressTimer = null;
        }
    }
    
    // 处理缩放开始
    handlePinchStart(e) {
        const touch1 = e.touches[0];
        const touch2 = e.touches[1];
        
        this.state.pinchDistance = this.getDistance(touch1, touch2);
        this.state.pinchCenter = this.getCenter(touch1, touch2);
        
        this.trigger('pinchstart', {
            distance: this.state.pinchDistance,
            center: this.state.pinchCenter
        });
    }
    
    // 处理缩放移动
    handlePinchMove(e) {
        const touch1 = e.touches[0];
        const touch2 = e.touches[1];
        
        const distance = this.getDistance(touch1, touch2);
        const center = this.getCenter(touch1, touch2);
        
        if (this.state.pinchDistance) {
            const scale = distance / this.state.pinchDistance;
            this.trigger('pinchmove', {
                scale: scale,
                distance: distance,
                center: center
            });
        }
    }
    
    // 获取两点距离
    getDistance(touch1, touch2) {
        const dx = touch1.clientX - touch2.clientX;
        const dy = touch1.clientY - touch2.clientY;
        return Math.sqrt(dx * dx + dy * dy);
    }
    
    // 获取两点中心
    getCenter(touch1, touch2) {
        return {
            x: (touch1.clientX + touch2.clientX) / 2,
            y: (touch1.clientY + touch2.clientY) / 2
        };
    }
    
    // 注册回调
    on(event, callback) {
        if (!this.callbacks[event]) {
            this.callbacks[event] = [];
        }
        this.callbacks[event].push(callback);
    }
    
    // 注销回调
    off(event, callback) {
        if (!this.callbacks[event]) return;
        
        const index = this.callbacks[event].indexOf(callback);
        if (index > -1) {
            this.callbacks[event].splice(index, 1);
        }
    }
    
    // 触发事件
    trigger(event, data = {}) {
        if (!this.callbacks[event]) return;
        
        this.callbacks[event].forEach(callback => {
            try {
                callback(data);
            } catch (e) {
                console.error(`手势事件回调执行失败 (${event}):`, e);
            }
        });
    }
    
    // 销毁
    destroy() {
        // 移除所有事件监听器
        this.element.removeEventListener('touchstart', this.handleTouchStart);
        this.element.removeEventListener('touchmove', this.handleTouchMove);
        this.element.removeEventListener('touchend', this.handleTouchEnd);
        this.element.removeEventListener('touchcancel', this.handleTouchCancel);
        this.element.removeEventListener('mousedown', this.handleMouseDown);
        this.element.removeEventListener('mousemove', this.handleMouseMove);
        this.element.removeEventListener('mouseup', this.handleMouseUp);
        this.element.removeEventListener('mouseleave', this.handleMouseLeave);
        this.element.removeEventListener('wheel', this.handleWheel);
        this.element.removeEventListener('contextmenu', this.handleContextMenu);
        
        document.removeEventListener('keydown', this.handleKeyDown);
        
        // 清除定时器
        this.clearLongPress();
        
        // 清空回调
        this.callbacks = {};
    }
}

// 简化的手势检测函数
ComicReader.gesture = function(element, options = {}) {
    return new ComicReader.GestureHandler(element, options);
};

// 为阅读器创建专用的手势处理器
ComicReader.createReaderGesture = function(imageContainer, callbacks = {}) {
    const gesture = new ComicReader.GestureHandler(imageContainer, {
        swipeThreshold: ComicReader.config.touchSensitivity || 50,
        doubleTapTimeout: 300
    });
    
    // 绑定阅读器特定的手势
    gesture.on('tap', (data) => {
        const rect = imageContainer.getBoundingClientRect();
        const clickX = data.x - rect.left;
        const width = rect.width;
        
        if (clickX < width / 3) {
            // 左侧点击 - 上一页
            callbacks.prevPage && callbacks.prevPage();
        } else if (clickX > (width * 2) / 3) {
            // 右侧点击 - 下一页
            callbacks.nextPage && callbacks.nextPage();
        } else {
            // 中间点击 - 切换控制栏
            callbacks.toggleControls && callbacks.toggleControls();
        }
    });
    
    gesture.on('doubletap', (data) => {
        // 双击缩放
        callbacks.toggleZoom && callbacks.toggleZoom(data);
    });
    
    gesture.on('swipeleft', () => {
        // 左滑 - 下一页
        callbacks.nextPage && callbacks.nextPage();
    });
    
    gesture.on('swiperight', () => {
        // 右滑 - 上一页
        callbacks.prevPage && callbacks.prevPage();
    });
    
    gesture.on('longpress', (data) => {
        // 长按 - 显示菜单
        callbacks.showMenu && callbacks.showMenu(data);
    });
    
    gesture.on('pinchstart', () => {
        // 开始缩放
        callbacks.startZoom && callbacks.startZoom();
    });
    
    gesture.on('pinchmove', (data) => {
        // 缩放中
        callbacks.zoom && callbacks.zoom(data);
    });
    
    return gesture;
};